package com.example.camerademo;


import java.io.IOException;
import java.lang.reflect.Method;
import java.util.List;

import android.content.Context;
import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.Paint;
import android.hardware.Camera;
import android.hardware.Camera.PreviewCallback;
import android.hardware.Camera.Size;
import android.os.Build;
import android.util.Log;
import android.view.SurfaceHolder;
import android.view.SurfaceView;
import android.hardware.Camera.*;






class Preview extends SurfaceView implements SurfaceHolder.Callback {
	private static final String TAG = "Preview";

    SurfaceHolder mHolder;
    public Camera camera;
    
    Preview(Context context) {
        super(context);
        
        // Install a SurfaceHolder.Callback so we get notified when the
        // underlying surface is created and destroyed.
        mHolder = getHolder();
        mHolder.addCallback(this);
        mHolder.setType(SurfaceHolder.SURFACE_TYPE_PUSH_BUFFERS);
    }

    public void surfaceCreated(SurfaceHolder holder) {
        // The Surface has been created, acquire the camera and tell it where
        // to draw.
    	// The Surface has been created, acquire the camera and tell it where
        // to draw.
        camera = Camera.open(); // <8>
        try {
          camera.setPreviewDisplay(holder);  // <9>

          camera.setPreviewCallback(new PreviewCallback() { // <10>
            // Called for each frame previewed
            public void onPreviewFrame(byte[] data, Camera camera) {  // <11>
              Log.d(TAG, "onPreviewFrame called at: " + System.currentTimeMillis());
              Preview.this.invalidate();  // <12>
            }
          });
        } catch (IOException e) { // <13>
          e.printStackTrace();
        }
    }

    public void surfaceDestroyed(SurfaceHolder holder) {
        // Surface will be destroyed when we return, so stop the preview.
        // Because the CameraDevice object is not a shared resource, it's very
        // important to release it when the activity is paused.
    	if (camera != null) {
            //camera.stopPreview();
            camera.setPreviewCallback(null);
            camera.release();
            camera = null;
        }
    }
    
    
    private Size getOptimalPreviewSize(List<Size> sizes, int w, int h) {

        final double ASPECT_TOLERANCE = 0.05;
        double targetRatio = (double) w / h;
        if (sizes == null) return null;

        Size optimalSize = null;
        double minDiff = Double.MAX_VALUE;

        int targetHeight = h;

        for (Size size : sizes) {
            double ratio = (double) size.width / size.height;
            if (Math.abs(ratio - targetRatio) > ASPECT_TOLERANCE) continue;
            if (Math.abs(size.height - targetHeight) < minDiff) {
                optimalSize = size;
                minDiff = Math.abs(size.height - targetHeight);
            }
        }

        if (optimalSize == null) {
            minDiff = Double.MAX_VALUE;
            for (Size size : sizes) {
                if (Math.abs(size.height - targetHeight) < minDiff) {
                    optimalSize = size;
                    minDiff = Math.abs(size.height - targetHeight);
                }
            }
        }

        return optimalSize;

    }

    private static Method getSupportedPreviewSizes = null;
    @SuppressWarnings("unchecked")
	public void surfaceChanged(SurfaceHolder holder, int format, int w, int h) {
      /*  // Now that the size is known, set up the camera parameters and begin
        // the preview.
        Camera.Parameters parameters = camera.getParameters();
        parameters.setPreviewSize(w, h);
        camera.setParameters(parameters);
        camera.startPreview();*/
    	

        try {
            Camera.Parameters parameters = camera.getParameters();

            Integer version = Integer.parseInt(Build.VERSION.SDK);

            if (version >= Build.VERSION_CODES.BASE) {

                try {
                    getSupportedPreviewSizes = Parameters.class.getMethod(
                            "getSupportedPreviewSizes", (Class[]) null);
                    /* success, this is a newer device */
                } catch (NoSuchMethodException nsme) {
                    /* failure, must be older device */
                }

                Object supportedFormats = getSupportedPreviewSizes.invoke(
                        parameters, (Object[]) null);
                List<Size> sizes;
                if (supportedFormats instanceof List<?>) {
                    sizes = (List<Camera.Size>) supportedFormats;// params.getSupportedPreviewSizes();
                    Size optimalSize = getOptimalPreviewSize(sizes, w, h);
                    parameters.setPreviewSize(optimalSize.width,
                            optimalSize.height);
                }
            } else {

                parameters.setPreviewSize(100, 100);
            }
            parameters.setPictureSize(320, 480);

            camera.setParameters(parameters);
            camera.startPreview();
        } catch (Exception e) {

            e.printStackTrace();
        }
    }

    @Override
    public void draw(Canvas canvas) {
    		super.draw(canvas);
    		Paint p= new Paint(Color.RED);
    		Log.d(TAG,"draw");
    		canvas.drawText("PREVIEW", canvas.getWidth()/2, canvas.getHeight()/2, p );
    }
}